package services

import (
	"bbs-go/internal/models"
	"fmt"
	"time"

	"github.com/mlogclub/simple/sqls"
)

type StatisticsService struct {
}

func NewStatisticsService() *StatisticsService {
	return &StatisticsService{}
}

// GetUserRegistrationTrendByDay 获取用户注册趋势（按天）
func (s *StatisticsService) GetUserRegistrationTrendByDay() ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7天）
	startTime := now.AddDate(0, 0, -7).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 按天统计
	var result []struct {
		Date  string `json:"date"`
		Count int64  `json:"count"`
	}
	err := sqls.DB().Model(&models.User{}).
		Select("DATE_FORMAT(FROM_UNIXTIME(create_time/1000), '%Y-%m-%d') as date, COUNT(*) as count").
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Group("date").
		Order("date ASC").
		Scan(&result).Error
	if err != nil {
		return nil, err
	}

	// 生成最近7天的日期列表
	var dates []string
	for i := 6; i >= 0; i-- {
		date := now.AddDate(0, 0, -i).Format("2006-01-02")
		dates = append(dates, date)
	}

	// 创建一个映射，用于快速查找日期对应的注册人数
	dateCountMap := make(map[string]int64)
	for _, item := range result {
		dateCountMap[item.Date] = item.Count
	}

	// 转换为前端需要的格式，确保所有日期都有数据
	var formattedResult []map[string]interface{}
	for _, date := range dates {
		count, exists := dateCountMap[date]
		if !exists {
			count = 0
		}
		formattedResult = append(formattedResult, map[string]interface{}{
			"date":  date,
			"count": count,
		})
	}

	return formattedResult, nil
}

// GetUserRegistrationTrendByWeek 获取用户注册趋势（按周）
func (s *StatisticsService) GetUserRegistrationTrendByWeek() ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7周）
	startTime := now.AddDate(0, 0, -7*7).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 按周统计
	var result []struct {
		Date  string `json:"date"`
		Count int64  `json:"count"`
	}
	err := sqls.DB().Model(&models.User{}).
		Select("DATE_FORMAT(FROM_UNIXTIME(create_time/1000), '%Y-%u') as date, COUNT(*) as count").
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Group("date").
		Order("date ASC").
		Scan(&result).Error
	if err != nil {
		return nil, err
	}

	// 生成最近7周的日期列表
	var dates []string
	for i := 6; i >= 0; i-- {
		// 计算当前周的开始日期
		weekStart := now.AddDate(0, 0, -i*7)
		year, week := weekStart.ISOWeek()
		date := fmt.Sprintf("%d-%02d", year, week)
		dates = append(dates, date)
	}

	// 创建一个映射，用于快速查找日期对应的注册人数
	dateCountMap := make(map[string]int64)
	for _, item := range result {
		dateCountMap[item.Date] = item.Count
	}

	// 转换为前端需要的格式，确保所有日期都有数据
	var formattedResult []map[string]interface{}
	for _, date := range dates {
		count, exists := dateCountMap[date]
		if !exists {
			count = 0
		}
		formattedResult = append(formattedResult, map[string]interface{}{
			"date":  date,
			"count": count,
		})
	}

	return formattedResult, nil
}

// GetUserRegistrationTrendByMonth 获取用户注册趋势（按月）
func (s *StatisticsService) GetUserRegistrationTrendByMonth() ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7个月）
	startTime := now.AddDate(0, -7, 0).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 按月统计
	var result []struct {
		Date  string `json:"date"`
		Count int64  `json:"count"`
	}
	err := sqls.DB().Model(&models.User{}).
		Select("DATE_FORMAT(FROM_UNIXTIME(create_time/1000), '%Y-%m') as date, COUNT(*) as count").
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Group("date").
		Order("date ASC").
		Scan(&result).Error
	if err != nil {
		return nil, err
	}

	// 生成最近7个月的日期列表
	var dates []string
	for i := 6; i >= 0; i-- {
		date := now.AddDate(0, -i, 0).Format("2006-01")
		dates = append(dates, date)
	}

	// 创建一个映射，用于快速查找日期对应的注册人数
	dateCountMap := make(map[string]int64)
	for _, item := range result {
		dateCountMap[item.Date] = item.Count
	}

	// 转换为前端需要的格式，确保所有日期都有数据
	var formattedResult []map[string]interface{}
	for _, date := range dates {
		count, exists := dateCountMap[date]
		if !exists {
			count = 0
		}
		formattedResult = append(formattedResult, map[string]interface{}{
			"date":  date,
			"count": count,
		})
	}

	return formattedResult, nil
}

// GetContentPublishingTrendByDay 获取内容发布趋势（按天）
func (s *StatisticsService) GetContentPublishingTrendByDay(contentType string) ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7天）
	startTime := now.AddDate(0, 0, -7).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 根据内容类型选择表
	var model interface{}
	switch contentType {
	case "topic":
		model = &models.Topic{}
	case "article":
		model = &models.Article{}
	default:
		model = &models.Topic{}
	}

	// 按天统计
	var result []struct {
		Date  string `json:"date"`
		Count int64  `json:"count"`
	}
	err := sqls.DB().Model(model).
		Select("DATE_FORMAT(FROM_UNIXTIME(create_time/1000), '%Y-%m-%d') as date, COUNT(*) as count").
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Group("date").
		Order("date ASC").
		Scan(&result).Error
	if err != nil {
		return nil, err
	}

	// 生成最近7天的日期列表
	var dates []string
	for i := 6; i >= 0; i-- {
		date := now.AddDate(0, 0, -i).Format("2006-01-02")
		dates = append(dates, date)
	}

	// 创建一个映射，用于快速查找日期对应的发布数
	dateCountMap := make(map[string]int64)
	for _, item := range result {
		dateCountMap[item.Date] = item.Count
	}

	// 转换为前端需要的格式，确保所有日期都有数据
	var formattedResult []map[string]interface{}
	for _, date := range dates {
		count, exists := dateCountMap[date]
		if !exists {
			count = 0
		}
		formattedResult = append(formattedResult, map[string]interface{}{
			"date":  date,
			"count": count,
		})
	}

	return formattedResult, nil
}

// GetContentPublishingTrendByWeek 获取内容发布趋势（按周）
func (s *StatisticsService) GetContentPublishingTrendByWeek(contentType string) ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7周）
	startTime := now.AddDate(0, 0, -7*7).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 根据内容类型选择表
	var model interface{}
	switch contentType {
	case "topic":
		model = &models.Topic{}
	case "article":
		model = &models.Article{}
	default:
		model = &models.Topic{}
	}

	// 按周统计
	var result []struct {
		Date  string `json:"date"`
		Count int64  `json:"count"`
	}
	err := sqls.DB().Model(model).
		Select("DATE_FORMAT(FROM_UNIXTIME(create_time/1000), '%Y-%u') as date, COUNT(*) as count").
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Group("date").
		Order("date ASC").
		Scan(&result).Error
	if err != nil {
		return nil, err
	}

	// 生成最近7周的日期列表
	var dates []string
	for i := 6; i >= 0; i-- {
		// 计算当前周的开始日期
		weekStart := now.AddDate(0, 0, -i*7)
		year, week := weekStart.ISOWeek()
		date := fmt.Sprintf("%d-%02d", year, week)
		dates = append(dates, date)
	}

	// 创建一个映射，用于快速查找日期对应的发布数
	dateCountMap := make(map[string]int64)
	for _, item := range result {
		dateCountMap[item.Date] = item.Count
	}

	// 转换为前端需要的格式，确保所有日期都有数据
	var formattedResult []map[string]interface{}
	for _, date := range dates {
		count, exists := dateCountMap[date]
		if !exists {
			count = 0
		}
		formattedResult = append(formattedResult, map[string]interface{}{
			"date":  date,
			"count": count,
		})
	}

	return formattedResult, nil
}

// GetContentPublishingTrendByMonth 获取内容发布趋势（按月）
func (s *StatisticsService) GetContentPublishingTrendByMonth(contentType string) ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7个月）
	startTime := now.AddDate(0, -7, 0).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 根据内容类型选择表
	var model interface{}
	switch contentType {
	case "topic":
		model = &models.Topic{}
	case "article":
		model = &models.Article{}
	default:
		model = &models.Topic{}
	}

	// 按月统计
	var result []struct {
		Date  string `json:"date"`
		Count int64  `json:"count"`
	}
	err := sqls.DB().Model(model).
		Select("DATE_FORMAT(FROM_UNIXTIME(create_time/1000), '%Y-%m') as date, COUNT(*) as count").
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Group("date").
		Order("date ASC").
		Scan(&result).Error
	if err != nil {
		return nil, err
	}

	// 生成最近7个月的日期列表
	var dates []string
	for i := 6; i >= 0; i-- {
		date := now.AddDate(0, -i, 0).Format("2006-01")
		dates = append(dates, date)
	}

	// 创建一个映射，用于快速查找日期对应的发布数
	dateCountMap := make(map[string]int64)
	for _, item := range result {
		dateCountMap[item.Date] = item.Count
	}

	// 转换为前端需要的格式，确保所有日期都有数据
	var formattedResult []map[string]interface{}
	for _, date := range dates {
		count, exists := dateCountMap[date]
		if !exists {
			count = 0
		}
		formattedResult = append(formattedResult, map[string]interface{}{
			"date":  date,
			"count": count,
		})
	}

	return formattedResult, nil
}

// GetHotTopicsByDay 获取热门话题（按天）
func (s *StatisticsService) GetHotTopicsByDay() ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7天）
	startTime := now.AddDate(0, 0, -7).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 查询热门话题
	var topics []models.Topic
	err := sqls.DB().Model(&models.Topic{}).
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Order("view_count + comment_count + like_count DESC").
		Limit(5).
		Find(&topics).Error
	if err != nil {
		return nil, err
	}

	// 转换为前端需要的格式
	var result []map[string]interface{}
	var sumScore int64 = 0
	for _, topic := range topics {
		hotScore := topic.ViewCount + topic.CommentCount + topic.LikeCount
		sumScore += hotScore
		result = append(result, map[string]interface{}{
			"id":           topic.Id,
			"title":        topic.Title,
			"viewCount":    topic.ViewCount,
			"commentCount": topic.CommentCount,
			"likeCount":    topic.LikeCount,
			"createTime":   topic.CreateTime,
			"hotScore":     hotScore,
		})
	}

	// 添加统计信息
	response := map[string]interface{}{
		"list":     result,
		"count":    len(result),
		"sumScore": sumScore,
	}

	return []map[string]interface{}{response}, nil
}

// GetHotTopicsByWeek 获取热门话题（按周）
func (s *StatisticsService) GetHotTopicsByWeek() ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7周）
	startTime := now.AddDate(0, 0, -7*7).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 查询热门话题
	var topics []models.Topic
	err := sqls.DB().Model(&models.Topic{}).
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Order("view_count + comment_count + like_count DESC").
		Limit(5).
		Find(&topics).Error
	if err != nil {
		return nil, err
	}

	// 转换为前端需要的格式
	var result []map[string]interface{}
	var sumScore int64 = 0
	for _, topic := range topics {
		hotScore := topic.ViewCount + topic.CommentCount + topic.LikeCount
		sumScore += hotScore
		result = append(result, map[string]interface{}{
			"id":           topic.Id,
			"title":        topic.Title,
			"viewCount":    topic.ViewCount,
			"commentCount": topic.CommentCount,
			"likeCount":    topic.LikeCount,
			"createTime":   topic.CreateTime,
			"hotScore":     hotScore,
		})
	}

	// 添加统计信息
	response := map[string]interface{}{
		"list":     result,
		"count":    len(result),
		"sumScore": sumScore,
	}

	return []map[string]interface{}{response}, nil
}

// GetHotTopicsByMonth 获取热门话题（按月）
func (s *StatisticsService) GetHotTopicsByMonth() ([]map[string]interface{}, error) {
	// 获取当前时间
	now := time.Now()

	// 计算时间范围（前7个月）
	startTime := now.AddDate(0, -7, 0).UTC().UnixMilli()
	endTime := now.UTC().UnixMilli()

	// 查询热门话题
	var topics []models.Topic
	err := sqls.DB().Model(&models.Topic{}).
		Where("create_time BETWEEN ? AND ?", startTime, endTime).
		Order("view_count + comment_count + like_count DESC").
		Limit(5).
		Find(&topics).Error
	if err != nil {
		return nil, err
	}

	// 转换为前端需要的格式
	var result []map[string]interface{}
	var sumScore int64 = 0
	for _, topic := range topics {
		hotScore := topic.ViewCount + topic.CommentCount + topic.LikeCount
		sumScore += hotScore
		result = append(result, map[string]interface{}{
			"id":           topic.Id,
			"title":        topic.Title,
			"viewCount":    topic.ViewCount,
			"commentCount": topic.CommentCount,
			"likeCount":    topic.LikeCount,
			"createTime":   topic.CreateTime,
			"hotScore":     hotScore,
		})
	}

	// 添加统计信息
	response := map[string]interface{}{
		"list":     result,
		"count":    len(result),
		"sumScore": sumScore,
	}

	return []map[string]interface{}{response}, nil
}
